import { ShallowRef, Ref, shallowRef, onBeforeUnmount } from 'vue'
import * as echarts from 'echarts'
import { ECharts, EChartsCoreOption } from 'echarts/core'
import { ChartType } from './type'
import * as ChartConfig from './config'

interface ChartHookOption {
	type?: Ref<ChartType>
	el: ShallowRef<HTMLElement>
	timeLoad?: boolean
}

/* 获取缩放比例全屏
 * @param {boolean} containRatio 是否计算设备像素比
 * @param {number | string} baseWidth 基础宽度
 */
export const getScale = (containRatio = true, baseWidth = 3030) => {
	const currentScale = document.documentElement.clientWidth / baseWidth
	const formattedScale = currentScale > 1 ? currentScale : 1
	const resultScale = containRatio ? formattedScale * window.devicePixelRatio : formattedScale
	return Math.ceil(resultScale)
}

/**
 *  视口变化时echart图表自适应调整
 */
class ChartsResize {
	#charts = new Set<ECharts>() // 缓存已经创建的图表实例
	#timeId = null
	constructor() {
		window.addEventListener('resize', this.handleResize.bind(this)) // 视口变化时调整图表
	}
	getCharts() {
		return [...this.#charts]
	}
	handleResize() {
		clearTimeout(this.#timeId)
		this.#timeId = setTimeout(() => {
			this.#charts.forEach((chart) => {
				chart.resize()
			})
		}, 500)
	}
	add(chart: ECharts) {
		this.#charts.add(chart)
	}
	remove(chart: ECharts) {
		this.#charts.delete(chart)
	}
	removeListener() {
		window.removeEventListener('resize', this.handleResize)
	}
}

export const chartsResize = new ChartsResize()

export const useCharts = ({ type, el, timeLoad }: ChartHookOption) => {
	const charts = shallowRef()
	let options!: EChartsCoreOption
	let initComplete = false

	const setOptions = (opt: EChartsCoreOption) => {
		initComplete && charts.value.setOption(opt)
	}

	const initChart = async (defaultOptions) => {
		charts.value = echarts.init(el.value, null, { devicePixelRatio: getScale() })
		if (ChartConfig[type.value]) {
			options = ChartConfig[type.value](defaultOptions)
		} else {
			options = defaultOptions
		}
		charts.value.setOption(options)
		if (timeLoad) SetTimeLoad(charts.value, options.dataset, options.series)
		chartsResize.add(charts.value) // 将图表实例添加到缓存中
		initComplete = true
		chartsResize.handleResize()
	}

	let interVal = null
	let currentIndex = -2
	const SetTimeLoad = (myChart, dataset, series) => {
		interVal = setInterval(() => {
			const dataArr = dataset ? dataset.source : series[0].data || []
			let dataLen = dataArr.length

			// 取消之前高亮的图形
			myChart.dispatchAction({
				type: 'downplay',
				seriesIndex: [0, 1],
				dataIndex: currentIndex,
			})
			currentIndex = (currentIndex + 1) % dataLen

			// 高亮当前图形
			myChart.dispatchAction({
				type: 'highlight',
				seriesIndex: [0, 1],
				dataIndex: currentIndex,
			})
			// 显示 tooltip
			myChart.dispatchAction({
				type: 'showTip',
				seriesIndex: series.length == 1 ? 0 : 1,
				dataIndex: currentIndex,
			})
		}, 2000)
	}

	onBeforeUnmount(() => {
		chartsResize.remove(charts.value) // 移除缓存
		clearInterval(interVal)
		interVal = null
	})

	return {
		charts,
		initChart,
		setOptions,
	}
}

export * from './type.d'
